package cn.zhx.xa.bi.config;

import cn.zhx.xa.bi.mq.BiMqConstant;
import org.springframework.amqp.core.*;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.HashMap;
import java.util.Map;

import static cn.zhx.xa.bi.mq.BiMqConstant.*;

@Configuration
public class RabbitMQConfig {
    /**
     * 普通队列交换机声明
     * 交换机类型：topic：处理路由键，按模式匹配，向符合规则的队列投递消息
     * name 交换机名称
     * durable 是否持久化
     * autoDelete 是否删除
     * arguments 用于设置其他参数
     * @return
     */
    @Bean
    public DirectExchange directExchange(){
        return new DirectExchange(BI_EXCHANGE_NAME);
    }

    /**
     * 声明普通队列，并设置与死信队列联系(该消息满足条件就会进入死信队列)
     * 一个队列设置了队列长度或者过期时间或被拒收，并且设置了死信队列的交换机和死信的路由key。那么消息满足条件就会进入死信队列。
     * name 队列名称
     * durable 是否持久化
     * exclusive 是否排外 如果是排外的，该队列 仅对首次声明它的连接（Connection）可见，是该Connection私有的，
     * 类似于加锁，并在连接断开connection.close()时自动删除
     * autoDelete 是否删除
     * arguments 用于设置其他参数
     * @return
     */
    @Bean
    public Queue directQueue(){
        Map<String, Object> queueArgs = new HashMap<>();
        // 通过设置 x-message-ttl 参数来指定消息的过期时间,时间为60秒
        queueArgs.put("x-message-ttl", 60000);
        //设置队列最大长度,测试使用
//        queueArgs.put("x-max-length",5);
        //设置死信队列交换机
        queueArgs.put("x-dead-letter-exchange",BI_DEAD_EXCHANGE_NAME);
        //设置死信队列路由key
        queueArgs.put("x-dead-letter-routing-key",BI_DEAD_ROUTING_KEY);
        // 参数解释：queueDeclare(String queue, boolean durable, boolean exclusive, boolean autoDelete, Map<String, Object> arguments)
        // durable: 持久化队列（重启后依然存在）
        // exclusive: 排他性队列（仅限此连接可见，连接关闭后队列删除）
        // autoDelete: 自动删除队列（无消费者时自动删除）
        return new Queue(BiMqConstant.BI_QUEUE_NAME,true, false, false,queueArgs);
    }

    /**
     * 将普通队列和交换机绑定
     */
    @Bean
    public Binding bingFormalQueue(){
        return BindingBuilder.bind(directQueue()).to(directExchange()).with(BI_ROUTING_KEY);
    }



    /**
     * 声明死信队列交换机
     * @return
     */
    @Bean
    public DirectExchange getDeadExchange(){
        return new DirectExchange(BI_DEAD_EXCHANGE_NAME,true,false,null);
    }


    /**
     * 声明死信队列
     * @return
     */
    @Bean
    public Queue getDeadQueue(){
        return new Queue(BI_DEAD_QUEUE_NAME,true,false,false, null);
    }

    /**
     * 将死信队列和交换机绑定
     * destination：目标队列或交换器
     * destinationType：DesdinationType指出目标是交换器还是对列
     * exchange：交换机
     * routingKey：路由key
     * arguments：参数设置
     * @return
     */
    @Bean
    public Binding bingDeadQueue(){
        return BindingBuilder.bind(getDeadQueue()).to(getDeadExchange()).with(BI_DEAD_ROUTING_KEY);
    }






}
